use crypto::digest::Digest;
use crypto::sha2::Sha256;
use rsa::Hash;
use rsa::{PaddingScheme, RsaPrivateKey};
use std::error::Error;
use std::iter::repeat;
use rsa::pkcs1::FromRsaPrivateKey;
pub enum HashType {
    Sha1,
    Sha256,
}

/// RSA签名
///
/// content: 签名内容
///
/// private_key: 私钥，PKCS#1
///
/// hash_type: hash类型
///
/// # Examples
///
/// ```
/// use sdk::sign::{SignUtil, HashType};
///
/// let content = String::from("123");
/// let private_key = String::from(私钥内容);
/// let sign = SignUtil::rsa_sign(content, private_key, HashType::Sha256);
///
/// println!("sign:{}", sign);
/// ```
/// return: 返回base64字符串
pub fn rsa_sign(
    content: String,
    private_key: String,
    hash_type: HashType,
) -> Result<String, Box<dyn Error>> { 
     // 格式化私钥
     let der_encoded = private_key
     .lines()
     .filter(|line| !line.starts_with("-"))
     .fold(String::new(), |mut data, line| {
         data.push_str(&line);
         data
     });
    let der_bytes = base64::decode(der_encoded)?;
    // 获取私钥对象
    let private_key = RsaPrivateKey::from_pkcs1_der(der_bytes.as_slice())?;

    // 创建一个Sha256对象
    let mut hasher = Sha256::new();
    // 对内容进行摘要
    hasher.input_str(content.as_str());
    // 将摘要结果保存到buf中
    let mut buf: Vec<u8> = repeat(0).take((hasher.output_bits() + 7) / 8).collect();
    hasher.result(&mut buf);

    // 对摘要进行签名
    let hash = match hash_type {
        HashType::Sha1 => Hash::SHA1,
        HashType::Sha256 => Hash::SHA2_256,
    };
    let sign_result = private_key.sign(
        PaddingScheme::PKCS1v15Sign {
            hash: Option::from(hash),
        },
        &buf,
    )?;

    Ok(base64::encode(sign_result))
}

pub fn rsa_verify(
    content: String,
    signature: String,
    public_certificate: String,
    hash_type: HashType,
) -> Result<bool, Box<dyn Error>> {
    todo!()
}

//

// 测试
#[cfg(test)]
mod tests {
    use crate::rsa_helper::{rsa_sign, HashType};

    #[test]
    fn it_works() {
        let content = String::from("123");
        let private_key = String::from("MIICXAIBAAKBgQCHJlAPN+1dCbgc3HiahQkT2W/skecGWOCkSX4CPvEc8oIk6544\nxihEwShHnfrapiQdF2fndv5agrhg4FyOHheST42L5MnCk+4Km+mWm5GDvmFS7Sa2\naZ5o3regY0MUoJ7D74dYjE3UYFuTujAXiXjGpAwa9qOcKotov5LCkSfUeQIDAQAB\nAoGAB1cyw8LYRQSHQCUO9Wiaq730jPNHSrJW4EGAIz/XMYjv/fCgx0lnDEX4CbzI\nUGoz/bME4R721YRyXoutJ0h14/cGrt/TEn/TMI0xnISzJHr8VSlyBkQEdfO/W3LO\nqjs/UYq2Bz4+kJROJHreM+7d5hiIWLzLBlyI8cSU92ySmHECQQDwju2SoRu88kQP\n1qr4seZyKQa8DHTVyCoa6LtPLXyJsdgWgY4KyqJHwMUumEC2Zhhu833CR0ZXbfta\nuQDmwAVJAkEAj9M225jrPasaD5vPO7thxtEqgV4F/ZyNKH0Z8bDH27KaKkQ+8GMt\nkxwKVckZXs2bMvg/6tCiDZkWAxawNrvFsQJBANmTrPWOmpQPW9gnhYRjA9gFm33C\nlno2DT9BeQloTtgL7zKMA3lnRdg4VyCJvR48waS4vupVpR228D1iT5pl22ECQF1M\nJUzkcM0rPheb+h2EW1QOgWU0Keyvbj4ykO7gv3T78dezN6TWoUzJpsapUiTWeXPh\n6AyZ1FW/1bChOiP3QLECQGAbObmsYlN0bjzPYChwWYeYjErXuv51a44GZCNWinFw\nGGiHU9ZAqF8RzmBVW4htwj0j/Yry/V1Sp0uoP0zu3uA=");
        let sign = rsa_sign(content, private_key, HashType::Sha256);
        println!("sign:{}", sign.unwrap());
    }
}
